#include "esp8266.h"
#include <stdio.h>
#include <string.h>
extern UART_HandleTypeDef huart2;
 uint8_t buffer[512]={0};
 uint16_t num=0;
void esp8266_init(void)
{
   HAL_GPIO_WritePin(GPIOB,GPIO_PIN_12,GPIO_PIN_RESET);

   HAL_Delay(20);
	
   HAL_GPIO_WritePin(GPIOB,GPIO_PIN_12,GPIO_PIN_SET);
   
   HAL_Delay(20);
    esp8266_response("chksum 0xde\r\n",2000);
		 HAL_Delay(50);
		 esp8266_setbaud(115200);
		 esp8266_response("ready\r\n",1000);

     printf("%s",buffer);
	   esp8266_send("ATE0");
		 memset(buffer,0,512);
     num=0;

}

uint8_t esp8266_response(const char*msg,uint32_t timeout)
{
     uint32_t Curtick=HAL_GetTick();//获取当前时间
	uint8_t data;
	uint8_t i=0;
     while(1)
		 {
		  if(HAL_GetTick()-Curtick>=timeout)//如果超时2s就break
				return 0;
			if(HAL_UART_Receive(&huart2,(uint8_t*)&data,1,10)==HAL_TIMEOUT)//如果10ms没收到esp8266发给单片机的数据，就返回HAL_TIMEOUT
				continue;      //如果初始化成功，不会HAL_TIMEOUT，就不continue;
			
			//printf("%c",data);   //单片机把串口2的数据一个字节一个字节读到data中，然后通过printf打印到串口1  //这里串口2的波特率为74880
		   buffer[num++]=data; 
		 if(data==msg[i])   //chksum 0xde\r\n  //匹配到的话，就是初始化成功
		 {
		   i++;
		    if(i==strlen(msg))
				{
				 return 1;
				
				}
		 
		 
		 
		 }
		 else   //重新匹配
		 {  i=0;

		 }
	 }




}

void esp8266_setbaud(uint32_t baud)
{

  huart2.Instance = USART2;
  huart2.Init.BaudRate = baud;
  huart2.Init.WordLength = UART_WORDLENGTH_8B;
  huart2.Init.StopBits = UART_STOPBITS_1;
  huart2.Init.Parity = UART_PARITY_NONE;
  huart2.Init.Mode = UART_MODE_TX_RX;
  huart2.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart2.Init.OverSampling = UART_OVERSAMPLING_16;
  HAL_UART_Init(&huart2);

}
void esp8266_send(const char* buffer)
{

HAL_UART_Transmit(&huart2,(uint8_t*)buffer,strlen(buffer),HAL_MAX_DELAY);
HAL_UART_Transmit(&huart2,(uint8_t*)"\r\n",2,HAL_MAX_DELAY);



}
void clearbuffer()
{
    printf("%s\r\n",buffer);
    memset((void*)buffer,0,512);  //清空缓冲区
    num=0;

}
uint8_t esp8266_link_wifi(const char*name,const char*password)
{
     char buffer[512];
		
		sprintf(buffer,"AT+CWJAP=\"%s\",\"%s\"",name,password);

    esp8266_send(buffer);
     
    if(esp8266_response("OK",2000))//esp8266串口收到
		{
		  
		  clearbuffer();
			return 1;
		}
		else
		{
		  clearbuffer();
			printf("connect fail\r\n");
		  return 0;
		}
		
	

}
uint8_t esp8266_connect_MQTT(const char*ip,int port,const char* user,const char* password)
{

   char buffer[512]={0};
	 
	 
	 
	 sprintf(buffer,"AT+MQTTUSERCFG=0,1,\"%s\",\"%s\",\"%s\",0,0,\" \"",ip,user,password);
   
	 esp8266_send(buffer);  //单片机向串口2发送构建的指令，串口2是esp8266,esp8266收到指令，esp8266从MQTT服务器获取用户信息保存在单片机中
   if(esp8266_response("OK\r\n",2000))   //esp8266串口收到
		{
		  
		  clearbuffer();     //向串口1发送   如果收到，构建成功
		}
		else                          //没收到单片机的构建命令      
		{
		  clearbuffer();     
			printf("config fail\r\n");
		
		}
		memset(buffer,0,512);   //清空构建命令的缓冲区
		
		
		sprintf(buffer,"AT+MQTTCONN=0,\"%s\",%d,1",ip,port);  //构建命令
		esp8266_send(buffer);  //单片机向串口2发送构建的指令，串口2是esp8266,esp8266收到指令，连接MQTT服务器
		  if(esp8266_response("OK\r\n",5000))   //esp8266串口收到
		{
		  
		  clearbuffer();     //向串口1发送   如果收到，连接成功
			return 1;
		}
		else                          //没收到单片机的构建命令      
		{
		  clearbuffer();     
			printf("connect fail\r\n");
		  return 0;
		}
		
		
		
		


}



void esp8266_Publish(const char* topic,const char*content)
{

    char buffer[512]={0};
		
		 sprintf(buffer,"AT+MQTTPUB=0,\"%s\",\"%s\",0,0",topic,content);
		 //printf("%s\r\n",content);
		 esp8266_send(buffer);  //单片机向串口2发送构建的指令，串口2是esp8266,esp8266收到指令,MQTT服务器得知发布请求

//		if(esp8266_response("OK\r\n",2000))   //esp8266串口收到，会给单片机返回OK，单片机Receive到esp8266的ok后，将其打印到串口1
//		{
//		  
//		  clearbuffer();     //向串口1发送   如果收到，连接成功
//		}
//		else                          //没收到单片机的构建命令      
//		{
//		  clearbuffer();     
//			printf("Publish fail\r\n");
//		
//		}


}

uint8_t esp8266_subscribe(const char* topic)
{

  char buffer[512]={0};
  sprintf(buffer,"AT+MQTTSUB=0,\"%s\",0",topic);
      esp8266_send(buffer);
  		if(esp8266_response("OK",10000))   //esp8266串口收到，会给单片机返回OK，单片机Receive到esp8266的ok后，将其打印到串口1
		{
		  
		  clearbuffer();     //向串口1发送   如果收到，连接成功
			return 1;
		}
		else                          //没收到单片机的构建命令      
		{
		  clearbuffer();     
			printf("subscribe fail\r\n");
		  return 0;
		}
	
	
	
	
}


















//void esp8266_connect_MQTT(const char*ip,int port,const char* user,const char* password)
//{
//    char buffer[256]={0};
//		sprintf(buffer,"AT+MQTTUSERCFG=0,1,\"0001\",\"%s\",\"%s\",0,0,\" \"",user,password);
//    
//		esp8266_send(buffer);
//		
//     if(esp8266_response("OK",1000))//esp8266串口收到
//		{
//		    //printf("is ok \r\n");
//		  clearbuffer();
//		}
//		else
//		{
//		  clearbuffer();
//			printf("MQTT config fail\r\n");
//		
//		}
//    // memset(buffer,0,sizeof(buffer));
//     sprintf(buffer,"AT+MQTTCONN=0,\"%s\",%d,1",ip,port);
//		  esp8266_send(buffer);
//		
//		   if(esp8266_response("OK",5000))//
//		{   printf("is ok \r\n");
//		    clearbuffer();
//		}
//		else
//		{
//		  clearbuffer();
//			printf("MQTT connect fail\r\n");
//		
//		}
//		



//}


//void esp8266_Publish(const char* topic,const char*content)   //发布
//{
//    char buffer[256]={0};
//		
//		sprintf(buffer,"AT+MQTTPUB=0,\"%s\",\"%s\",0,0",topic,content);
//    	esp8266_send(buffer);
//		
//		   if(esp8266_response("OK",10000))
//		{
//		    
//		  clearbuffer();
//		}
//		else
//		{
//		  clearbuffer();
//			printf("MQTT Publish fail\r\n");
//		
//		}
//    


//}


//void esp8266_subscribe(const char* topic)  //订阅
//{


//   char buffer[512]={0};
//	 sprintf(buffer,"AT+MQTTSUB=0,\"%s\",0",topic);
//   esp8266_send(buffer);
//   

//   	   if(esp8266_response("OK",10000))
//		{
//		    
//		  clearbuffer();
//		}
//		else
//		{
//		  clearbuffer();
//			printf("MQTT subscribe fail\r\n");
//		
//		}






//}

		 

